package com.fingard.dsp.bank.directbank.nnbill01;

import com.fingard.constant.Format;
import com.fingard.dsp.bank.directConfig.ActSetItem;
import com.fingard.dsp.bank.directbank.RefundState;
import com.fingard.dsp.bank.directbank.bankInterface.IRecRefund;
import com.fingard.dsp.bank.directbank.nnbill01.md5.MD5Util;
import com.fingard.dsp.bank.directbank.nnbill01.wsdl.gatewayrefund.GatewayRefundQuery;
import com.fingard.dsp.bank.directbank.nnbill01.wsdl.gatewayrefund.GatewayRefundQueryServiceLocator;
import com.fingard.dsp.bank.directbank.nnbill01.wsdl.gatewayrefund.dto.GatewayRefundQueryRequest;
import com.fingard.dsp.bank.directbank.nnbill01.wsdl.gatewayrefund.dto.GatewayRefundQueryResponse;
import com.fingard.dsp.bank.directbank.nnbill01.wsdl.gatewayrefund.dto.GatewayRefundQueryResultDto;
import com.fingard.dsp.bank.reqrespobj.recrefund.ReqQryRecRefund;
import com.fingard.dsp.bank.reqrespobj.recrefund.ReqRecRefund;
import com.fingard.dsp.bank.reqrespobj.recrefund.RetAtsQryRecRefund;
import com.fingard.dsp.bank.reqrespobj.recrefund.RetAtsRecRefund;
import com.fingard.util.DateHelper;
import com.fingard.xml.XmlTextReader;

import java.util.Date;

public class NNBill01RecRefund extends NNBill01Base implements IRecRefund {
    @Override
    public RetAtsRecRefund submitRecRefund(ReqRecRefund p_reqRef) throws Exception {
        RetAtsRecRefund retAts = new RetAtsRecRefund();
        retAts.oriRdSeq = p_reqRef.oriRdSeq;
        retAts.refundNo = p_reqRef.refundNo;

        try {
            ActSetItem actItem = this.getBankConfig().getActSetItem(p_reqRef.ownAct, "*");
            if (actItem != null) {
                String macVal = "";
                String macVals = "";
                macVal = appendParam(macVal, "merchant_id", actItem.inMerchantId);
                macVals = appendParams(macVals, "merchant_id", actItem.inMerchantId);
                macVal = appendParam(macVal, "version", "bill_drawback_api_1");
                macVals = appendParams(macVals, "version", "bill_drawback_api_1");
                macVal = appendParam(macVal, "command_type", "001");
                macVals = appendParams(macVals, "command_type", "001");
                macVal = appendParam(macVal, "orderid", p_reqRef.oriRdSeq);
                macVals = appendParams(macVals, "orderid", p_reqRef.oriRdSeq);
                macVal = appendParam(macVal, "amount", p_reqRef.amount);
                macVals = appendParams(macVals, "amount", p_reqRef.amount);
                String tmpDate = Format.DateTime14Format.format(new Date());
                macVal = appendParam(macVal, "postdate", tmpDate);
                macVals = appendParams(macVals, "postdate", tmpDate);
                macVal = appendParam(macVal, "txOrder", p_reqRef.refundNo);
                macVals = appendParams(macVals, "txOrder", p_reqRef.refundNo);
                macVals = appendParams(macVals, "merchant_key", actItem.saltKeyMap.get("submit"));

                this.WriteBankLogLn("签名原始数据为:" + macVals);
                String mac = MD5Util.md5Hex(macVals.getBytes(getCharset())).toUpperCase();
                macVal = appendParam(macVal, "mac", mac);

                this.WriteBankLogStep2(macVal);
                WriteBankUrlLogLn(bankFront.getUrl("gwRefundSubmit"));

                String[] tmpStrRet = sendToBank(macVal, bankFront.getUrl("gwRefundSubmit"));
                if (tmpStrRet[0].length() == 0) {
                    StringBuilder tmpSbMsg = new StringBuilder();
                    //解析银行返回
                    XmlTextReader tmpBkReader = loadBankRespXmlReader(tmpStrRet[1], tmpSbMsg);
                    if (tmpBkReader != null) {
                        while (tmpBkReader.read("/DRAWBACKAPI")) {
                            retAts.respCode = "0";
                            String result = tmpBkReader.readedXElement.getSingleTextNotNull("RESULT");
                            String tmpRespCode = tmpBkReader.readedXElement.getSingleTextNotNull("CODE");
                            if ("Y".equals(result)) {
                                retAts.refundState = RefundState.REFUND_SUCCESS;
                            } else if ("N".equals(result)) {
                                retAts.refundState = RefundState.REFUND_FAIL;
                            }
                            retAts.originalCode = tmpRespCode;
                            retAts.respInfo = tmpRespCode;
                            retAts.oriOppOrderNo = tmpBkReader.readedXElement.getSingleTextNotNull("ORDERID");
                            //渠道流水号 transaction_id
                            retAts.originalInfo = tmpRespCode;
                            retAts.unifiedCode = getBankConfig().getMapValueByKey("recRefundMapping", retAts.originalCode);
                        }
                    } else {
                        retAts.respCode = "-1";
                        retAts.respInfo = tmpStrRet[1];
                    }
                } else {
                    retAts.respCode = "-1";
                    retAts.respInfo = tmpStrRet[1];
                }
            } else {
                retAts.respCode = "0";
                retAts.respInfo = "未找到账号[" + p_reqRef.ownAct + "]商户配置信息!";
                retAts.refundState = RefundState.REFUND_FAIL;
                retAts.originalCode = "E9981";
                retAts.originalInfo = retAts.respInfo;
                retAts.unifiedCode = "E9981";
            }
        } catch (Exception ex) {
            ex.printStackTrace();
            retAts.respCode = "-1";
            retAts.respInfo = ex.getMessage();
            WriteBankLogLn(ex);
        }

        return retAts;
    }

    @Override
    public RetAtsQryRecRefund queryRecRefund(ReqQryRecRefund p_reqQryRef) throws Exception {
        RetAtsQryRecRefund retAts = new RetAtsQryRecRefund();
        retAts.oriRdSeq = p_reqQryRef.oriRdSeq;
        retAts.refundNo = p_reqQryRef.refundNo;
        try {
            ActSetItem actItem = this.getBankConfig().getActSetItem(p_reqQryRef.ownAct, "");
            if (actItem != null) {
                String version = "v2.0";
                String signType = "1";
                String merchantAcctId = actItem.merchantId;
                String startDate = Format.Date8Format.format(DateHelper.addDays(Format.DateTimeFormat.parse(p_reqQryRef.refundSentDate), -1));
                String endDate = Format.Date8Format.format(DateHelper.addDays(Format.DateTimeFormat.parse(p_reqQryRef.refundSentDate), 1));
                String lastUpdateStartDate = "";
                String lastUpdateEndDate = "";
                String orderId = p_reqQryRef.refundNo;
                String requestPage = "1";
                String rOrderId = p_reqQryRef.oriRdSeq;
                String seqId = "";
                String status = "";
                String extra_output_column = "payType";
                String key = actItem.saltKey;

                String macVal = "";
                String macVals = "";
                macVal = appendParam(macVal, "version", version);
                macVal = appendParam(macVal, "signType", signType);
                macVal = appendParam(macVal, "merchantAcctId", merchantAcctId);
                macVal = appendParam(macVal, "startDate", startDate);
                macVal = appendParam(macVal, "endDate", endDate);
                macVal = appendParam(macVal, "lastUpdateStartDate", lastUpdateStartDate);
                macVal = appendParam(macVal, "lastUpdateEndDate", lastUpdateEndDate);
                macVal = appendParam(macVal, "orderId", orderId);
                macVal = appendParam(macVal, "requestPage", requestPage);
                macVal = appendParam(macVal, "rOrderId", rOrderId);
                macVal = appendParam(macVal, "seqId", seqId);
                macVal = appendParam(macVal, "status", status);
                macVal = appendParam(macVal, "extra_output_column", extra_output_column);

                macVals = appendParam(macVal, "key", key);
                this.WriteBankLogLn("签名原始数据为:" + macVals);
                String signMsg = MD5Util.md5Hex(macVals.getBytes(getCharset())).toUpperCase();
                macVal = appendParam(macVal, "signMsg", signMsg);
                System.setProperty("jdk.tls.client.protocols", "TLSv1.2");

                GatewayRefundQueryServiceLocator gl = new GatewayRefundQueryServiceLocator();
                gl.setgatewayRefundQueryEndpointAddress(bankFront.getUrl("gwRefundQuery"));
                GatewayRefundQuery grQuery = gl.getgatewayRefundQuery();
                GatewayRefundQueryRequest dto = new GatewayRefundQueryRequest();
                dto.setVersion(version);
                dto.setSignType(signType);
                dto.setMerchantAcctId(merchantAcctId);
                dto.setStartDate(startDate);
                dto.setEndDate(endDate);
                dto.setLastupdateStartDate(lastUpdateStartDate);
                dto.setLastupdateEndDate(lastUpdateEndDate);
                dto.setOrderId(orderId);
                dto.setRequestPage(requestPage);
                dto.setROrderId(rOrderId);
                dto.setSeqId(seqId);
                dto.setStatus(status);
                dto.setExtra_output_column(extra_output_column);
                dto.setSignMsg(signMsg);

                this.WriteBankLogStep2(macVal);
                GatewayRefundQueryResponse queryResponse = grQuery.query(dto);

                this.WriteBankLogStep3(convertParams(queryResponse));
                retAts.respCode = "0";
                String errCode = queryResponse.getErrCode();
                if (errCode != null && !"".equals(errCode)) {
                    retAts.respCode = "-1";
                    retAts.respInfo = errCode;
                } else {
                    GatewayRefundQueryResultDto[] results = queryResponse.getResults();
                    if (results != null) {
                        for (int i = 0; i < results.length; i++) {
                            retAts.respInfo = results[i].getFailReason();
                            String respStatus = results[i].getStatus();
                            if ("1".equals(respStatus)) {
                                retAts.refundState = RefundState.REFUND_SUCCESS;
                            } else if ("2".equals(status)) {
                                retAts.refundState = RefundState.REFUND_FAIL;
                            } else {
                                retAts.refundState = RefundState.REFUND_PAYING;
                            }
                            retAts.oriOppOrderNo = results[i].getROrderId();
                            retAts.originalCode = results[i].getFailReason();
                            retAts.originalInfo = results[i].getFailReason();
                            retAts.unifiedCode = getBankConfig().getMapValueByKey("recRefundMapping", retAts.originalCode);
                        }
                    }
                }
            } else {
                retAts.respCode = "-1";
                retAts.respInfo = "未找到账号[" + p_reqQryRef.ownAct + "]商户配置信息,请检查config.xml中当前账号相关配置信息!";
            }
        } catch (Exception ex) {
            ex.printStackTrace();
            retAts.respCode = "-1";
            retAts.respInfo = ex.getMessage();
            WriteBankLogLn(ex);
        }
        return retAts;
    }
}